package com.example.backend.service;

import com.example.backend.domain.entity.Ticket;
import com.example.backend.domain.entity.User;
import com.example.backend.domain.enums.Role;
import com.example.backend.domain.enums.TicketStatus;
import com.example.backend.repository.TicketRepository;
import com.example.backend.repository.UserRepository;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.time.Instant;
import java.time.temporal.ChronoUnit;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * 仪表板服务
 * 根据用户角色提供不同的仪表板数据
 */
@Service
public class DashboardService {

    @Autowired
    private TicketRepository ticketRepository;

    @Autowired
    private UserRepository userRepository;

    /**
     * 获取仪表板概览数据
     * 根据用户角色返回相应的概览信息
     */
    public Map<String, Object> getDashboardOverview(User user) {
        Map<String, Object> overview = new HashMap<>();
        
        switch (user.getRole()) {
            case ADMIN:
                overview = getAdminOverview();
                break;
            case AGENT:
                overview = getAgentOverview(user);
                break;
            case CUSTOMER:
                overview = getCustomerOverview(user);
                break;
            default:
                overview = getDefaultOverview();
        }
        
        // 添加用户基本信息
        overview.put("user", Map.of(
            "id", user.getId(),
            "username", user.getUsername(),
            "fullName", user.getFullName(),
            "role", user.getRole().name().toLowerCase(),
            "lastLoginAt", user.getLastLoginAt()
        ));
        
        return overview;
    }

    /**
     * 获取仪表板统计数据
     */
    public Map<String, Object> getDashboardStatistics(User user) {
        Map<String, Object> statistics = new HashMap<>();
        
        switch (user.getRole()) {
            case ADMIN:
                statistics = getAdminStatistics();
                break;
            case AGENT:
                statistics = getAgentStatistics(user);
                break;
            case CUSTOMER:
                statistics = getCustomerStatistics(user);
                break;
            default:
                statistics = getDefaultStatistics();
        }
        
        return statistics;
    }

    /**
     * 获取最近活动
     */
    public Map<String, Object> getRecentActivities(User user) {
        Map<String, Object> activities = new HashMap<>();
        
        switch (user.getRole()) {
            case ADMIN:
                activities = getAdminRecentActivities();
                break;
            case AGENT:
                activities = getAgentRecentActivities(user);
                break;
            case CUSTOMER:
                activities = getCustomerRecentActivities(user);
                break;
            default:
                activities = getDefaultRecentActivities();
        }
        
        return activities;
    }

    /**
     * 获取工单趋势图表数据
     */
    public Map<String, Object> getTicketTrendChart(User user) {
        Map<String, Object> chartData = new HashMap<>();
        
        switch (user.getRole()) {
            case ADMIN:
                chartData = getAdminTicketTrendChart();
                break;
            case AGENT:
                chartData = getAgentTicketTrendChart(user);
                break;
            case CUSTOMER:
                chartData = getCustomerTicketTrendChart(user);
                break;
            default:
                chartData = getDefaultTicketTrendChart();
        }
        
        return chartData;
    }

    /**
     * 获取工单状态图表数据
     */
    public Map<String, Object> getTicketStatusChart(User user) {
        Map<String, Object> chartData = new HashMap<>();
        
        switch (user.getRole()) {
            case ADMIN:
                chartData = getAdminTicketStatusChart();
                break;
            case AGENT:
                chartData = getAgentTicketStatusChart(user);
                break;
            case CUSTOMER:
                chartData = getCustomerTicketStatusChart(user);
                break;
            default:
                chartData = getDefaultTicketStatusChart();
        }
        
        return chartData;
    }

    // ==================== 管理员相关方法 ====================

    private Map<String, Object> getAdminOverview() {
        Instant now = Instant.now();
        Instant oneWeekAgo = now.minus(7, ChronoUnit.DAYS);
        Instant oneMonthAgo = now.minus(30, ChronoUnit.DAYS);

        Map<String, Object> overview = new HashMap<>();
        overview.put("totalTickets", ticketRepository.count());
        overview.put("openTickets", ticketRepository.countByStatus(TicketStatus.OPEN));
        overview.put("inProgressTickets", ticketRepository.countByStatus(TicketStatus.IN_PROGRESS));
        overview.put("resolvedTickets", ticketRepository.countByStatus(TicketStatus.RESOLVED));
        overview.put("closedTickets", ticketRepository.countByStatus(TicketStatus.CLOSED));
        overview.put("totalUsers", userRepository.count());
        overview.put("activeUsers", userRepository.countByLastLoginAtAfter(oneWeekAgo));
        overview.put("newTicketsThisWeek", ticketRepository.countByCreatedAtAfter(oneWeekAgo));
        overview.put("newTicketsThisMonth", ticketRepository.countByCreatedAtAfter(oneMonthAgo));
        overview.put("avgResolutionTime", calculateAverageResolutionTime());
        overview.put("slaCompliance", calculateSlaCompliance());
        return overview;
    }

    private Map<String, Object> getAdminStatistics() {
        Instant now = Instant.now();
        Instant oneWeekAgo = now.minus(7, ChronoUnit.DAYS);

        return Map.of(
            "ticketStats", Map.of(
                "total", ticketRepository.count(),
                "thisWeek", ticketRepository.countByCreatedAtAfter(oneWeekAgo),
                "urgent", ticketRepository.countByPriority(com.example.backend.domain.enums.TicketPriority.URGENT),
                "high", ticketRepository.countByPriority(com.example.backend.domain.enums.TicketPriority.HIGH)
            ),
            "userStats", Map.of(
                "total", userRepository.count(),
                "active", userRepository.countByLastLoginAtAfter(oneWeekAgo),
                "admins", userRepository.countByRole(Role.ADMIN),
                "agents", userRepository.countByRole(Role.AGENT),
                "customers", userRepository.countByRole(Role.CUSTOMER)
            ),
            "performanceStats", Map.of(
                "avgResolutionTime", calculateAverageResolutionTime(),
                "slaCompliance", calculateSlaCompliance(),
                "firstResponseTime", calculateFirstResponseTime()
            )
        );
    }

    private Map<String, Object> getAdminRecentActivities() {
        List<Ticket> recentTickets = ticketRepository.findTop10ByOrderByCreatedAtDesc();
        return Map.of(
            "recentTickets", recentTickets.stream().map(ticket -> Map.of(
                "id", ticket.getId(),
                "title", ticket.getTitle(),
                "status", ticket.getStatus().name(),
                "priority", ticket.getPriority().name(),
                "createdBy", ticket.getCreatedBy().getUsername(),
                "createdAt", ticket.getCreatedAt()
            )).toList(),
            "recentUsers", userRepository.findTop5ByOrderByCreatedAtDesc().stream().map(user -> Map.of(
                "id", user.getId(),
                "username", user.getUsername(),
                "role", user.getRole().name(),
                "createdAt", user.getCreatedAt()
            )).toList()
        );
    }

    private Map<String, Object> getAdminTicketTrendChart() {
        // 返回最近30天的工单趋势数据
        return Map.of(
            "labels", generateDateLabels(30),
            "datasets", List.of(
                Map.of(
                    "label", "新建工单",
                    "data", generateTicketTrendData(30),
                    "borderColor", "rgb(75, 192, 192)",
                    "backgroundColor", "rgba(75, 192, 192, 0.2)"
                ),
                Map.of(
                    "label", "已解决工单",
                    "data", generateResolvedTrendData(30),
                    "borderColor", "rgb(54, 162, 235)",
                    "backgroundColor", "rgba(54, 162, 235, 0.2)"
                )
            )
        );
    }

    private Map<String, Object> getAdminTicketStatusChart() {
        return Map.of(
            "labels", List.of("待处理", "处理中", "已解决", "已关闭"),
            "datasets", List.of(Map.of(
                "data", List.of(
                    ticketRepository.countByStatus(TicketStatus.OPEN),
                    ticketRepository.countByStatus(TicketStatus.IN_PROGRESS),
                    ticketRepository.countByStatus(TicketStatus.RESOLVED),
                    ticketRepository.countByStatus(TicketStatus.CLOSED)
                ),
                "backgroundColor", List.of(
                    "rgba(255, 99, 132, 0.8)",
                    "rgba(255, 205, 86, 0.8)",
                    "rgba(75, 192, 192, 0.8)",
                    "rgba(54, 162, 235, 0.8)"
                )
            ))
        );
    }

    // ==================== 客服相关方法 ====================

    private Map<String, Object> getAgentOverview(User user) {
        return Map.of(
            "assignedTickets", ticketRepository.countByAssignedTo(user),
            "openTickets", ticketRepository.countByAssignedToAndStatus(user, TicketStatus.OPEN),
            "inProgressTickets", ticketRepository.countByAssignedToAndStatus(user, TicketStatus.IN_PROGRESS),
            "resolvedTickets", ticketRepository.countByAssignedToAndStatus(user, TicketStatus.RESOLVED),
            "avgResolutionTime", calculateAgentAverageResolutionTime(user),
            "ticketsThisWeek", ticketRepository.countByAssignedToAndCreatedAtAfter(user, Instant.now().minus(7, ChronoUnit.DAYS))
        );
    }

    private Map<String, Object> getAgentStatistics(User user) {
        Instant oneWeekAgo = Instant.now().minus(7, ChronoUnit.DAYS);
        
        return Map.of(
            "assignedStats", Map.of(
                "total", ticketRepository.countByAssignedTo(user),
                "thisWeek", ticketRepository.countByAssignedToAndCreatedAtAfter(user, oneWeekAgo),
                "urgent", ticketRepository.countByAssignedToAndPriority(user, com.example.backend.domain.enums.TicketPriority.URGENT),
                "high", ticketRepository.countByAssignedToAndPriority(user, com.example.backend.domain.enums.TicketPriority.HIGH)
            ),
            "performanceStats", Map.of(
                "avgResolutionTime", calculateAgentAverageResolutionTime(user),
                "responseRate", calculateAgentResponseRate(user),
                "satisfactionScore", calculateAgentSatisfactionScore(user)
            )
        );
    }

    private Map<String, Object> getAgentRecentActivities(User user) {
        List<Ticket> recentTickets = ticketRepository.findTop10ByAssignedToOrderByCreatedAtDesc(user);
        return Map.of(
            "recentTickets", recentTickets.stream().map(ticket -> Map.of(
                "id", ticket.getId(),
                "title", ticket.getTitle(),
                "status", ticket.getStatus().name(),
                "priority", ticket.getPriority().name(),
                "customer", ticket.getCustomer().getUsername(),
                "createdAt", ticket.getCreatedAt()
            )).toList()
        );
    }

    private Map<String, Object> getAgentTicketTrendChart(User user) {
        return Map.of(
            "labels", generateDateLabels(30),
            "datasets", List.of(
                Map.of(
                    "label", "分配的工单",
                    "data", generateAgentTicketTrendData(user, 30),
                    "borderColor", "rgb(75, 192, 192)",
                    "backgroundColor", "rgba(75, 192, 192, 0.2)"
                )
            )
        );
    }

    private Map<String, Object> getAgentTicketStatusChart(User user) {
        return Map.of(
            "labels", List.of("待处理", "处理中", "已解决"),
            "datasets", List.of(Map.of(
                "data", List.of(
                    ticketRepository.countByAssignedToAndStatus(user, TicketStatus.OPEN),
                    ticketRepository.countByAssignedToAndStatus(user, TicketStatus.IN_PROGRESS),
                    ticketRepository.countByAssignedToAndStatus(user, TicketStatus.RESOLVED)
                ),
                "backgroundColor", List.of(
                    "rgba(255, 99, 132, 0.8)",
                    "rgba(255, 205, 86, 0.8)",
                    "rgba(75, 192, 192, 0.8)"
                )
            ))
        );
    }

    // ==================== 客户相关方法 ====================

    private Map<String, Object> getCustomerOverview(User user) {
        return Map.of(
            "myTickets", ticketRepository.countByCustomer(user),
            "openTickets", ticketRepository.countByCustomerAndStatus(user, TicketStatus.OPEN),
            "inProgressTickets", ticketRepository.countByCustomerAndStatus(user, TicketStatus.IN_PROGRESS),
            "resolvedTickets", ticketRepository.countByCustomerAndStatus(user, TicketStatus.RESOLVED),
            "ticketsThisWeek", ticketRepository.countByCustomerAndCreatedAtAfter(user, Instant.now().minus(7, ChronoUnit.DAYS))
        );
    }

    private Map<String, Object> getCustomerStatistics(User user) {
        Instant oneWeekAgo = Instant.now().minus(7, ChronoUnit.DAYS);
        
        return Map.of(
            "ticketStats", Map.of(
                "total", ticketRepository.countByCustomer(user),
                "thisWeek", ticketRepository.countByCustomerAndCreatedAtAfter(user, oneWeekAgo),
                "urgent", ticketRepository.countByCustomerAndPriority(user, com.example.backend.domain.enums.TicketPriority.URGENT),
                "high", ticketRepository.countByCustomerAndPriority(user, com.example.backend.domain.enums.TicketPriority.HIGH)
            )
        );
    }

    private Map<String, Object> getCustomerRecentActivities(User user) {
        List<Ticket> recentTickets = ticketRepository.findTop10ByCustomerOrderByCreatedAtDesc(user);
        return Map.of(
            "recentTickets", recentTickets.stream().map(ticket -> Map.of(
                "id", ticket.getId(),
                "title", ticket.getTitle(),
                "status", ticket.getStatus().name(),
                "priority", ticket.getPriority().name(),
                "assignedTo", ticket.getAssignedTo() != null ? ticket.getAssignedTo().getUsername() : "未分配",
                "createdAt", ticket.getCreatedAt()
            )).toList()
        );
    }

    private Map<String, Object> getCustomerTicketTrendChart(User user) {
        return Map.of(
            "labels", generateDateLabels(30),
            "datasets", List.of(
                Map.of(
                    "label", "我的工单",
                    "data", generateCustomerTicketTrendData(user, 30),
                    "borderColor", "rgb(75, 192, 192)",
                    "backgroundColor", "rgba(75, 192, 192, 0.2)"
                )
            )
        );
    }

    private Map<String, Object> getCustomerTicketStatusChart(User user) {
        return Map.of(
            "labels", List.of("待处理", "处理中", "已解决"),
            "datasets", List.of(Map.of(
                "data", List.of(
                    ticketRepository.countByCustomerAndStatus(user, TicketStatus.OPEN),
                    ticketRepository.countByCustomerAndStatus(user, TicketStatus.IN_PROGRESS),
                    ticketRepository.countByCustomerAndStatus(user, TicketStatus.RESOLVED)
                ),
                "backgroundColor", List.of(
                    "rgba(255, 99, 132, 0.8)",
                    "rgba(255, 205, 86, 0.8)",
                    "rgba(75, 192, 192, 0.8)"
                )
            ))
        );
    }

    // ==================== 默认方法 ====================

    private Map<String, Object> getDefaultOverview() {
        return Map.of("message", "未知用户角色");
    }

    private Map<String, Object> getDefaultStatistics() {
        return Map.of("message", "未知用户角色");
    }

    private Map<String, Object> getDefaultRecentActivities() {
        return Map.of("message", "未知用户角色");
    }

    private Map<String, Object> getDefaultTicketTrendChart() {
        return Map.of("message", "未知用户角色");
    }

    private Map<String, Object> getDefaultTicketStatusChart() {
        return Map.of("message", "未知用户角色");
    }

    // ==================== 辅助方法 ====================

    private Double calculateAverageResolutionTime() {
        // 计算平均解决时间（小时）
        return 24.0; // 示例数据
    }

    private Double calculateSlaCompliance() {
        // 计算SLA合规率
        return 95.5; // 示例数据
    }

    private Double calculateFirstResponseTime() {
        // 计算首次响应时间（小时）
        return 2.5; // 示例数据
    }

    private Double calculateAgentAverageResolutionTime(User user) {
        // 计算客服平均解决时间
        return 18.0; // 示例数据
    }

    private Double calculateAgentResponseRate(User user) {
        // 计算客服响应率
        return 98.0; // 示例数据
    }

    private Double calculateAgentSatisfactionScore(User user) {
        // 计算客服满意度评分
        return 4.5; // 示例数据
    }

    private List<String> generateDateLabels(int days) {
        // 生成日期标签
        return List.of("1天前", "2天前", "3天前", "4天前", "5天前", "6天前", "7天前");
    }

    private List<Integer> generateTicketTrendData(int days) {
        // 生成工单趋势数据
        return List.of(5, 8, 12, 6, 9, 15, 11);
    }

    private List<Integer> generateResolvedTrendData(int days) {
        // 生成解决工单趋势数据
        return List.of(3, 6, 10, 4, 7, 12, 9);
    }

    private List<Integer> generateAgentTicketTrendData(User user, int days) {
        // 生成客服工单趋势数据
        return List.of(2, 3, 5, 2, 4, 6, 4);
    }

    private List<Integer> generateCustomerTicketTrendData(User user, int days) {
        // 生成客户工单趋势数据
        return List.of(1, 2, 3, 1, 2, 4, 2);
    }
}
